import {createRouter, createWebHashHistory} from 'vue-router'
import store from '@/store'
import request from '@/utils/request'
import {getToken, removeToken} from '@/utils/auth'
import BlankRoute from '@/components/BlankRoute'

// 静态路由
const routes = [
    {
        path: '',
        name: 'layout',
        component: () => import('@/views/layout/index.vue'),
        redirect: '/dashboard',
        children: [
            {
                path: '/dashboard',
                name: 'dashboard',
                component: () => import('@/views/dashboard/index.vue'),
                meta: {title: '首页'}
            },
            {
                path: '/personal/profile',
                component: () => import('@/views/personal/profile/index.vue'),
                meta: {title: '个人信息'}
            },
            {
                path: '/personal/changePassword',
                component: () => import('@/views/personal/change_password/index.vue'),
                meta: {title: '修改密码'}
            }
        ]
    },
    {
        path: '/login',
        component: () => import('@/views/login/index.vue')
    },
    {
        path: '/403',
        component: () => import('@/views/_error/403.vue')
    },
    {
        path: '/404',
        component: () => import('@/views/_error/404.vue')
    },
    {
        path: '/500',
        component: () => import('@/views/_error/500.vue')
    }
]

const router = createRouter({
    history: createWebHashHistory(),
    routes,
    scrollBehavior: () => {
        return {top: 0}
    }
})

// 免登录白名单
const whiteList = ['/login', '/403', '/404', '/500']

// 路由导航前置守卫
router.beforeEach(async (to, from, next) => {
    // 设置页面标题
    document.title = to.meta.title || 'BECE'
    // 判断是否登录
    if (!getToken()) {
        // 在免登录白名单中的直接放行，其它的重定向到登录页面
        whiteList.includes(to.path) ? next() : next(`/login?redirect=${to.path}`)
        return
    }
    // 判断是否已经获取过菜单
    if (store.state.menus.length > 0) {
        // 如果没有找到匹配的路由，转到404页面，否则直接进入
        to.matched.length === 0 ? next('/404') : next()
        return
    }
    // 发送同步请求，获取菜单
    const {data} = await request.get('/api/routes')
    if (data && data.length) {
        store.commit('setMenus', data)
        await addDynamicRoutes(data)
        next({...to, replace: true})
    } else {
        // 如果没有菜单路由，清空登录信息
        removeToken()
        next('/403') // 跳转到403页面
    }
})

// 添加动态路由
function addDynamicRoutes(menuList) {
    const routes = mapRoutes(menuList)
    routes.forEach(route => router.addRoute('layout', route))
}

// 递归生成路由
function mapRoutes(menuList) {
    return menuList.map(menu => {
        const route = {
            path: menu.path || `${menu.id}`,
            name: menu.name,
            meta: {
                title: menu.name,
                icon: menu.icon || null
            }
        }
        if (menu.component?.length) {
            route.component = () => import(`@/views/${menu.component}`)
                .catch(() => {
                    return import('@/views/_error/404.vue')
                })
        } else {
            route.redirect = 'noRedirect'
            route.component = BlankRoute
        }
        if (menu.children && menu.children.length > 0) {
            route.children = mapRoutes(menu.children)
        }
        return route
    })
}

export default router
